package com.marmot.cloud.framework.core.response;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.ReflectUtil;
import com.marmot.cloud.framework.core.pager.Order;
import com.marmot.cloud.framework.core.pager.Pager;
import com.marmot.cloud.framework.core.pager.Sorter;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.Accessors;
import org.springframework.data.domain.Page;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

@Data
@Accessors(chain = true)
@AllArgsConstructor
@NoArgsConstructor
@Schema(description = "返回结果内容对象")
public class PageData<T> {
    @Schema(description = "返回内容对象")
    List<T> content;
    @Schema(description = "返回分页对象")
    Pager pager;
    @Schema(description = "返回排序对象")
    Sorter sorter;

    private PageData(Page<T> pagers) {
        this.content = pagers.getContent();
        this.pager = new Pager(pagers.getPageable().getPageNumber() + 1, pagers.getPageable().getPageSize(), pagers.getTotalElements());
        this.sorter = new Sorter().setOrders(pagers.getSort().stream().map(item ->
                new Order(item.getProperty(), item.getDirection().name())).collect(Collectors.toList()));
    }

    public static <T> PageData<T> of(Page<T> pagers) {
        return new PageData(pagers);
    }

    public static <S, T> PageData<T> of(Page<S> sources, Class<T> target) {
        List<T> list = new ArrayList();
        for (S source :
                sources.getContent()) {
            T t = ReflectUtil.newInstanceIfPossible(target);
            BeanUtil.copyProperties(source, t);
            list.add(t);
        }
        PageData<T> pageData = new PageData<>();
        pageData.setContent(list);
        pageData.setPager(new Pager(sources.getPageable().getPageNumber() + 1, sources.getPageable().getPageSize(), sources.getTotalElements()));
        pageData.setSorter(new Sorter().setOrders(sources.getSort().stream().map(item -> new Order(item.getProperty(), item.getDirection().name())).collect(Collectors.toList())));
        return pageData;
    }

    public <T> PageData<T> converter(Class<T> tClass) {
        PageData<T> pageData = new PageData<>();
        pageData.setSorter(this.getSorter());
        pageData.setPager(this.getPager());
        List<T> list = BeanUtil.copyToList(this.getContent(), tClass);
        pageData.setContent(list);
        return pageData;
    }

}
